#region

using System;
using System.Collections;
using System.IO;
using System.Text;
using Microsoft.SharePoint;

#endregion

namespace SpWiki.Lib.Repository
{
    public class SpWikiFile
    {
        #region Constructor

        private SpWikiFile()
        {
        }

        public SpWikiFile(Guid listId, int itemId)
        {
            ListId = listId;
            ItemId = itemId;

            SPList list = SPContext.Current.Site.RootWeb.Lists[ListId];
            SPListItem item = list.GetItemById(ItemId);
            if (item.File != null)
            {
                _file = item.File;
            }
        }

        #endregion Constructor

        /// <summary>
        /// The wiki file.
        /// </summary>
        private readonly SPFile _file;

        #region Properties


        /// <summary>
        /// Gets the view URL.
        /// Should be like http://dev01/sites/mediawiki/_layouts/SpWiki/Forms/View.aspx?SpWikiList={BC03DD5F-EFA9-4768-BD39-0487CA441A9E}&SpWikiID=2
        /// </summary>
        public string ViewUrl
        {
            get
            {
                var webUrl = _file.Web.Site.MakeFullUrl(_file.Web.ServerRelativeUrl);
                const string aspx = "/_layouts/SpWiki/Forms/View.aspx";
                var url = string.Concat(webUrl, "/", aspx, "?SpWikiList={", ListId, "}&SpWikiID=", ItemId);
                //var absUrl = (string)_file.Item[SPBuiltInFieldId.EncodedAbsUrl];
                //var fullUrl = _file.Web.Site.MakeFullUrl(_file.Web.ServerRelativeUrl);
                return url;

            }
        }


        /// <summary>
        /// Gets the edit URL.
        /// Should be like http://dev01/sites/mediawiki/_layouts/SpWiki/Forms/Edit.aspx?SpWikiList={BC03DD5F%2DEFA9%2D4768%2DBD39%2D0487CA441A9E}&SpWikiID=2
        /// </summary>
        public string EditUrl
        {
            get
            {
                var webUrl = _file.Web.Site.MakeFullUrl(_file.Web.ServerRelativeUrl);
                const string aspx = "/_layouts/SpWiki/Forms/Edit.aspx";
                var url = string.Concat(webUrl, "/", aspx, "?SpWikiList={", ListId, "}&SpWikiID=", ItemId);
                return url;

            }
        }

        public string Title
        {
            get { return _file.Title; }
        }

        /// <summary>
        /// The wiki document library
        /// </summary>
        private SPDocumentLibrary _library;

        /// <summary>
        /// The web.
        /// </summary>
        private SPWeb _web;

        /// <summary>
        /// Gets or sets the raw content of a wiki page.
        /// </summary>
        /// <value>
        /// The content.
        /// </value>
        public string RawContent
        {
            get
            {
                using (var reader = new StreamReader(_file.OpenBinaryStream()))
                {
                    return reader.ReadToEnd();
                }
            }
            set { SaveRawContent(value, Library, ParentFolder, FileName); }
        }

        /// <summary>
        /// Gets the name of the file.
        /// </summary>
        /// <value>
        /// The name of the file.
        /// </value>
        private string FileName
        {
            get { return _file.Name; }
        }

        /// <summary>
        /// Gets the parent folder.
        /// </summary>
        private SPFolder ParentFolder
        {
            get { return _file.ParentFolder; }
        }

        /// <summary>
        /// Gets the web.
        /// </summary>
        private SPWeb Web
        {
            get { return _web ?? (_web = Library.ParentWeb); }
        }

        /// <summary>
        /// Gets the wiki document library.
        /// </summary>
        internal SPDocumentLibrary Library
        {
            get { return _library ?? (_library = _file.Item.ParentList as SPDocumentLibrary); }
        }

        /// <summary>
        /// Gets or sets the wiki document library id.
        /// </summary>
        /// <value>
        /// The wiki document library id.
        /// </value>
        private Guid ListId { get; set; }

        /// <summary>
        /// Gets or sets the wiki item id.
        /// </summary>
        /// <value>
        /// The wiki item id.
        /// </value>
        private int ItemId { get; set; }

        #endregion  Properties

        #region Methods

        /// <summary>
        /// Saves the content.
        /// </summary>
        /// <param name="content">The content.</param>
        /// <param name="wikiLibrary">The wiki library.</param>
        /// <param name="folder">The folder.</param>
        /// <param name="path">The path.</param>
        /// <returns></returns>
        public void SaveRawContent(string content, SPDocumentLibrary wikiLibrary, SPFolder folder, string path)
        {
            try
            {
                byte[] byteArray = Encoding.UTF8.GetBytes(content);
                var contentStream = new MemoryStream(byteArray);
                var properties = new Hashtable
                                     {
                                         {"ContentType", "SPWiki"},
                                         {"ContentTypeId", wikiLibrary.ContentTypes["SPWiki"].Id.ToString()}
                                     };

                var file = folder.Files.Add(path, contentStream, properties, true);
                file.Update();
            }
            catch (Exception ex)
            {
                //todo exception handling
            }
        }

        #endregion  Methods       
    }
}